<template>
  <view class="calendar">
    <view class="year-month">
      <picker class="date" mode="date" @change="Picker"
        >{{ today.year }} 年 - {{ today.month }} 月
      </picker>
    </view>
    <view
      v-if="!showCalendar"
      class="day-box"
      @touchstart="TapStartDay"
      @touchmove="TouchMoveDay"
      @touchend="TapEndDay"
    >
      <view
        v-for="(item, index) in days"
        :key="index"
        class="day-item"
        :class="[
          item.left >= centerPointLeft && item.right <= centerPointRight
            ? 'day-item-active'
            : '',
        ]"
        :style="{
          left: `${item.left}px`,
          transition: `${labelTransition}`,
          opacity: `${leftBoundary - latticeWidth / 2 <= item.left && item.right <= rightBoundary + latticeWidth / 2 ? '1' : '0'}`,
        }"
        @tap="SelectDay(index)"
        >{{ item.day }}</view
      >
    </view>
    <view
      v-else
      class="detail-box"
      :style="{
        opacity: `${showCalendar && calOpacityBtn ? 100 : 0}%`,
      }"
    >
      <view class="content">
        <view
          v-for="(row, rowIndex) in nowMonth.data"
          :key="rowIndex"
          class="row"
        >
          <view
            v-for="(col, colIndex) in row"
            :key="colIndex"
            class="col"
            :class="[col.active ? 'col-active' : '']"
            @tap="tapCalendar(col.day, rowIndex, colIndex)"
          >
            <view class="col-day">{{ col.day }} </view>
            <view :class="[col.pay<0?'col-pay-red':col.pay===0?'col-pay-gray':'col-pay-yellow']">{{ col.pay<0?-col.pay:col.pay }} </view>
          </view>
        </view>
      </view>
    </view>
    <!-- <view
      class="show-soldier"
      :style="{
        borderTop: `${!showCalendar ? '5px solid rgb(233, 232, 232)' : ''}`,
        borderBottom: `${showCalendar ? '5px solid rgb(233, 232, 232)' : ''}`,
      }"
      @tap="show(!showCalendar)"
    ></view> -->
  </view>
</template>

<script setup lang="ts">
import { reactive, ref } from 'vue';
import type { todayType } from '@/types/bill';
import { onShow, onHide, onLoad } from '@dcloudio/uni-app';
import { useBillStore } from '@/stores/bill';

////变量区
const billStore = useBillStore();
const systemInfo = uni.getSystemInfoSync();
const screenWidth = systemInfo.windowWidth;
const centerPoint = screenWidth / 2;
const interval = (screenWidth * 10) / 750;
const latticeWidth = (screenWidth * 60) / 750;
const leftBoundary = centerPoint - latticeWidth * 3.5 - 6 * interval;
const rightBoundary = centerPoint + latticeWidth * 3.5 + 6 * interval;
const centerPointLeft = centerPoint - latticeWidth / 2 - interval * 2;
const centerPointRight = centerPoint + latticeWidth / 2 + interval * 2;
let today = ref<todayType>({
  year: 0,
  month: 0,
  day: 0,
});
let days = ref<
  Array<{
    day: number;
    month: number;
    year: number;
    left: number;
    right: number;
    center: number;
    showCenter: number;
    showLeft: number;
    showRight: number;
  }>
>([]);
let touch = { start: 0, move: 0 };
let labelTransition = ref<string>('opacity ease 0.5s');
let daySelectBtn = true;
let showCalendar = ref<boolean>(false);
let nowMonth = reactive({
  dayNum: 0,
  firstDay: 0,
  data: [],
  bill: [],
});
let calShow = false;
let calOpacityBtn = ref<boolean>(false);

////函数区
onLoad(() => {
  console.log('calendar Load');
});
onShow(() => {
  console.log('calendar Show');
});
onHide(() => {
  console.log('calendar Hide');
});

//重新选举
function Elect(index: number) {
  daySelectBtn = false;
  labelTransition.value = 'all ease 0.5s';
  setTimeout(function () {
    labelTransition.value = '';
    uni.$emit('dayData', {
      year: days.value[index].year,
      month: days.value[index].month,
      day: days.value[index].day,
    });
    setTimeout(function () {
      labelTransition.value = 'opacity ease 0.5s';
      daySelectBtn = true;
    }, 100);
  }, 500);
}
//选择横条日期
function SelectDay(index: number) {
  if (daySelectBtn) {
    console.log('点击日期',index);
    let temp = centerPoint - days.value[index].center;
    labelTransition.value = 'all ease 0.5s';
    days.value.filter((item) => {
      item.left += temp;
      item.right += temp;
      item.center += temp;
      item.showCenter = item.center;
      item.showLeft = item.left;
      item.showRight = item.right;
    });
    Elect(index);
  }
}
// 大面板左移动
uni.$on('boardLeft', function (calendarBtn) {
  if(calendarBtn){
    today.value.month = Number(today.value.month)+1
    uni.$emit('dayData', today.value);
    show(true);
  }else{
    SelectDay(7)
  }

})
uni.$on('boardRight', function (calendarBtn) {
  if(calendarBtn){
    today.value.month = Number(today.value.month)-1
    uni.$emit('dayData', today.value);
    show(true);
  }else{
    SelectDay(5)
  }
})
// 点击日历
function tapCalendar(day: number, rowIndex: number, colIndex: number) {
  if(day){
    nowMonth.data.forEach((item) => {
      item.forEach((item1) => {
        item1.active = false;
      });
    });
    nowMonth.data[rowIndex][colIndex].active = true;
    GetDays(today.value.year, today.value.month, day);
    uni.$emit('dayData', {
      year: today.value.year,
      month: today.value.month,
      day: day,
    });
  }
}
//触摸日期横条
function TapStartDay(event: TouchEvent) {
  if (daySelectBtn) {
    labelTransition.value = 'opacity ease 0.5s';
    touch.start = event.touches[0].clientX;
    touch.move = 0;
  }
}
//滑动日期横条
function TouchMoveDay(event: TouchEvent) {
  if (daySelectBtn) {
    touch.move = -(touch.start - event.touches[0].clientX);
    days.value.filter((item) => {
      item.left = touch.move + item.showLeft;
      item.right = touch.move + item.showRight;
      item.center = touch.move + item.showCenter;
    });
  }
}
//离开日期横条
function TapEndDay() {
  if (daySelectBtn) {
    //看看谁离中心点最近
    if (touch.move !== 0) {
      let minTemp = 10000;
      let indexTemp = 0;
      days.value.filter((item, index) => {
        if (Math.abs(minTemp) >= Math.abs(item.center - centerPoint)) {
          minTemp = centerPoint - item.center;
          indexTemp = index;
        }
      });
      labelTransition.value = 'all ease 0.5s';
      days.value.filter((item) => {
        item.left += minTemp;
        item.right += minTemp;
        item.center += minTemp;
        item.showCenter = item.center;
        item.showLeft = item.left;
        item.showRight = item.right;
      });
      Elect(indexTemp);
    }
  }
}
//日期选择器
function Picker(event: { detail: { value: string } }) {
  let temp = event.detail.value;
  today.value.year = Number(temp.split('-')[0]);
  today.value.month = Number(temp.split('-')[1]);
  today.value.day = Number(temp.split('-')[2]);
  uni.$emit('dayData', today.value);
  show(true);
}
//获取数据
uni.$on('dayData', function (data) {
  today.value = data;
  GetDays(today.value.year, today.value.month, today.value.day);
});
//获取当月的天数
function GetDayInmonth(year: number, month: number) {
  return new Date(year, month, 0).getDate();
}
//获取基于指定年月日的间隔多少天的日期
function ChoreDays(year: number, month: number, day: number, index: number) {
  let dayTemp = day;
  let monthTemp = month;
  let yearTemp = year;
  let dayInmonthTemp = GetDayInmonth(year, month);

  //获取日期差
  dayTemp = day + index;

  //如果小于0说明在上一个月
  if (dayTemp <= 0) {
    monthTemp = month - 1;
    if (monthTemp <= 0) {
      monthTemp = 12;
      yearTemp = year - 1;
    } else {
      yearTemp = year;
    }
    dayInmonthTemp = GetDayInmonth(yearTemp, monthTemp);
    dayTemp = dayInmonthTemp - Math.abs(dayTemp);
  } else if (dayTemp > dayInmonthTemp) {
    //说明在下一个月
    monthTemp = month + 1;
    if (monthTemp >= 13) {
      monthTemp = 1;
      yearTemp = year + 1;
    } else {
      yearTemp = year;
    }
    dayTemp = dayTemp - dayInmonthTemp;
  }
  return {
    day: dayTemp,
    year: yearTemp,
    month: monthTemp,
    left: 0,
    right: 0,
    center: 0,
  };
}
//获取7天
function GetDays(year: number, month: number, day: number) {
  days.value = [];
  for (let i = -6; i <= 6; i++) {
    days.value.push(ChoreDays(year, month, day, i));
  }
  SetDays();
}
//计算日期格子的布局参数
function SetDays() {
  // 计算中心宽度
  const systemInfo = uni.getSystemInfoSync();
  const screenWidth = systemInfo.screenWidth;
  const centerWidth = screenWidth / 2;
  // 中心索引
  const centerIndex = (days.value.length - 1) / 2;
  // 计算中点
  days.value[centerIndex].center = centerWidth;
  days.value[centerIndex].left =
    days.value[centerIndex].center - latticeWidth / 2;
  days.value[centerIndex].right =
    days.value[centerIndex].center + latticeWidth / 2;
  days.value[centerIndex].showLeft = days.value[centerIndex].left;
  days.value[centerIndex].showCenter = days.value[centerIndex].center;
  days.value[centerIndex].showRight = days.value[centerIndex].right;

  let num = 0;
  for (let i = centerIndex - 1; i >= 0; i--) {
    num++;
    days.value[i].center = centerWidth - num * (latticeWidth + interval);
    days.value[i].left = days.value[i].center - latticeWidth / 2;
    days.value[i].right = days.value[i].center + latticeWidth / 2;
    days.value[i].showLeft = days.value[i].left;
    days.value[i].showCenter = days.value[i].center;
    days.value[i].showRight = days.value[i].right;
  }
  num = 0;
  for (let i = centerIndex + 1; i < days.value.length; i++) {
    num++;
    days.value[i].center = centerWidth + num * (latticeWidth + interval);
    days.value[i].left = days.value[i].center - latticeWidth / 2;
    days.value[i].right = days.value[i].center + latticeWidth / 2;
    days.value[i].showLeft = days.value[i].left;
    days.value[i].showCenter = days.value[i].center;
    days.value[i].showRight = days.value[i].right;
  }
}
// 展开日历
function show(show: boolean) {
  showCalendar.value = show;
  if (!showCalendar.value) {
    calOpacityBtn.value = false;
    calShow = false;
    uni.$emit('calendarShow', false);
  } else {
    calShow = true;
    setTimeout(() => {
      calOpacityBtn.value = true;
    }, 200);
    uni.$emit('calendarShow', true);
    nowMonth.dayNum = getMonthDays(today.value.year, today.value.month);
    nowMonth.firstDay = getNowMonthDayForWeek(
      today.value.year,
      today.value.month,
    );
    nowMonth.data = getCalendar(nowMonth.dayNum, nowMonth.firstDay);
    let { days } = GetMonthData();
    days.sort((a, b) => a.day - b.day);
    nowMonth.bill = days;
    nowMonth.data.forEach((item) => {
      item.forEach((item1) => {
        let temp = days.find((dayItem) => dayItem.day === item1.day);
        if (temp) {
          item1.pay =Number((-temp.cost+(temp.receipts??0)).toFixed(2))
        }
      });
    });
  }
}
//获取今日数据
function GetMonthData() {
  return billStore.GetMonth(
    today.value.year,
    today.value.month,
    today.value.day,
  );
}

function getCalendar(dayNum: number, firstDay: number) {
  let temp = [];
  let row = [];
  for (let i = 0; i < firstDay; i++) {
    row.push({});
  }
  for (let i = 1; i <= dayNum; i++) {
    let active = false;
    if (today.value.day === i) {
      active = true;
    }
    row.push({
      day: i,
      pay: 0,
      active: active,
    });
    if (row.length === 7) {
      temp.push(row);
      row = [];
    }
  }
  while (row.length < 7) {
    row.push({});
  }
  temp.push(row);
  return temp;
}
// 获取指定年和月的一个月天数
function getMonthDays(year: number, month: number) {
  // 创建一个Date对象，设置年份和月份（注意：月份是从0开始的）
  // 将日期设置为下一个月的第0天，这样就能得到上一个月的最后一天，即这个月的天数
  var date = new Date(year, month, 0);
  return date.getDate();
}
// 获取指定年月的月第一天是星期几
function getNowMonthDayForWeek(year: number, month: number): number {
  // 创建一个日期对象，设置为指定年月的第1天
  const firstDayOfMonth = new Date(year, month - 1, 1);
  // 返回这一天是星期几
  return firstDayOfMonth.getDay();
}
uni.$on('showCalByIndex', function (btn) {
  if (calShow || btn) {
    show(btn);
  }
});
</script>

<style scoped>
.calendar {
  width: 100%;
  height: 100%;
  background: white;
  border-radius: 15px;
  position: relative;
  transition: all ease 0.5s;
}
.detail-box {
  height: 85%;
  width: 100%;
  bottom: 0;
  position: absolute;
  display: flex;
  justify-content: center;
  align-items: center;
  transition: all ease 0.2s;
}
.content {
  width: 80%;
  height: 90%;
  display: flex;
  flex-direction: column;
  justify-content: space-around;
}
.row {
  flex: 1;
  width: 100%;
  display: flex;
  justify-content: space-between;
  height: 8%;
}
.col {
  height: 100%;
  flex: 1;
  display: flex;
  flex-direction: column;
  justify-content: center;
  align-items: center;
  margin: 1%;
}
.col-day {
  font-size: 30rpx;
  color: rgb(118, 118, 118);
}
.col-pay-red {
  font-size: 20rpx;
  color: rgb(139, 36, 36);
}
.col-pay-gray {
  font-size: 20rpx;
  color: rgb(203, 203, 203);
}
.col-pay-yellow {
  font-size: 20rpx;
  color: rgb(222, 193, 66);
}
.col-active {
  color: rgb(122, 118, 118);
  background: rgb(243, 243, 243);
  border-radius: 10px;
}
.show-soldier {
  transition: all ease 0.5s;
  position: absolute;
  right: 2%;
  bottom: 7%;
  border-left: 10px solid transparent; /* 左侧边框透明 */
  border-right: 10px solid transparent; /* 右侧边框透明 */
}
.year-month {
  position: absolute;
  height: 50%;
  width: 100%;
  display: flex;
  align-items: start;
  justify-content: center;
}
.day-box {
  width: 750rpx;
  height: 50%;
  display: flex;
  bottom: 0;
  align-items: center;
  position: absolute;
}
.day-item {
  top: 10%;
  position: absolute;
  display: flex;
  justify-content: center;
  align-items: center;
  width: 60rpx;
  height: 60rpx;
  font-size: 33rpx;
  border-radius: 10px;
  color: rgb(200, 199, 199);
  /* transform: translate(50%); */
}
.day-item-active {
  color: rgb(122, 118, 118);
  background: rgb(243, 243, 243);
}
.date {
  width: 50%;
  transform: translateY(70%);
  position: absolute;
  display: flex;
  justify-content: center;
  align-items: start;
  font-size: 37rpx;
  color: rgb(58, 58, 58);
}
</style>
